<!DOCTYPE html>
<html>
<head>
    <title>Physics Diagram</title>
    <style>
        body {
            display: flex;
            justify-content: center;
            align-items: center;
            height: 100vh;
            margin: 0;
            background-color: #f0f0f0;
        }
        canvas {
            border: 1px solid #ccc;
            background-color: #fff;
        }
    </style>
</head>
<body>
    <canvas id="physicsCanvas" width="450" height="450"></canvas>
    <script>
        const canvas = document.getElementById('physicsCanvas');
        const ctx = canvas.getContext('2d');

        // Style settings
        ctx.strokeStyle = 'black';
        ctx.fillStyle = 'black';
        ctx.lineWidth = 1.5;
        ctx.textAlign = 'center';
        ctx.textBaseline = 'middle';

        // Coordinates and dimensions
        const originX = 100;
        const originY = 60;
        const D = 100; // Pixel length for D
        const axisLen = 280;
        const circleRadius = 8;
        const arrowHeadSize = 8;
        
        // Helper function to draw an arrowhead
        function drawArrow(ctx, fromx, fromy, tox, toy, headlen) {
            const dx = tox - fromx;
            const dy = toy - fromy;
            const angle = Math.atan2(dy, dx);
            ctx.beginPath();
            ctx.moveTo(fromx, fromy);
            ctx.lineTo(tox, toy);
            ctx.stroke();
            
            ctx.beginPath();
            ctx.moveTo(tox, toy);
            ctx.lineTo(tox - headlen * Math.cos(angle - Math.PI / 6), toy - headlen * Math.sin(angle - Math.PI / 6));
            ctx.lineTo(tox - headlen * Math.cos(angle + Math.PI / 6), toy - headlen * Math.sin(angle + Math.PI / 6));
            ctx.closePath();
            ctx.fill();
        }

        // 1. Draw Coordinate System and Liquid Surface
        // Vertical axis (x-axis)
        drawArrow(ctx, originX, originY, originX, originY + axisLen, arrowHeadSize);
        // Horizontal line (liquid surface)
        ctx.beginPath();
        ctx.moveTo(originX, originY);
        ctx.lineTo(originX + 280, originY);
        ctx.stroke();

        // 2. Draw Labels
        // Font settings
        const regularFont = '20px Arial';
        const italicFont = 'italic 20px Times New Roman';
        const smallFont = '14px Arial';
        const captionFont = '20px KaiTi, serif';

        // 'O' at the origin
        ctx.font = italicFont;
        ctx.fillText('O', originX - 20, originY + 5);

        // 'x' axis label
        ctx.fillText('x', originX - 20, originY + axisLen + 5);
        
        // '液面' (Liquid Surface)
        ctx.font = captionFont;
        ctx.fillText('液面', originX + 150, originY - 20);

        // 'ρ₀' label
        ctx.font = italicFont;
        ctx.fillText('ρ', originX + 295, originY + 8);
        ctx.font = smallFont;
        ctx.fillText('₀', originX + 305, originY + 14);

        // 3. Draw depth markers and objects
        const y_D_half = originY + D / 2;
        const y_D = originY + D;

        // Dashed lines
        ctx.save();
        ctx.setLineDash([5, 5]);
        ctx.lineWidth = 1;

        // Line at D/2
        ctx.beginPath();
        ctx.moveTo(originX, y_D_half);
        ctx.lineTo(originX + 180, y_D_half);
        ctx.stroke();

        // Line at D
        ctx.beginPath();
        ctx.moveTo(originX, y_D);
        ctx.lineTo(originX + 300, y_D);
        ctx.stroke();

        ctx.restore();

        // Label 'D/2'
        ctx.textAlign = 'center';
        ctx.font = italicFont;
        ctx.fillText('D', originX - 30, y_D_half - 10);
        ctx.beginPath();
        ctx.moveTo(originX - 40, y_D_half);
        ctx.lineTo(originX - 20, y_D_half);
        ctx.stroke();
        ctx.font = regularFont;
        ctx.fillText('2', originX - 30, y_D_half + 12);

        // Label 'D'
        ctx.font = italicFont;
        ctx.fillText('D', originX - 30, y_D + 8);
        
        // Label '2ρ₀'
        ctx.font = regularFont;
        ctx.fillText('2', originX + 315, y_D + 8);
        ctx.font = italicFont;
        ctx.fillText('ρ', originX + 328, y_D + 8);
        ctx.font = smallFont;
        ctx.fillText('₀', originX + 338, y_D + 14);
        
        // Circle at D/2
        const circle1X = originX + 130;
        ctx.beginPath();
        ctx.arc(circle1X, y_D_half, circleRadius, 0, 2 * Math.PI);
        ctx.stroke();

        // 4. Free-Body Diagram
        const fbd_X = originX + 90;
        const fbd_Y = y_D + 80;
        const forceLen = 50;

        // Circle for FBD
        ctx.beginPath();
        ctx.arc(fbd_X, fbd_Y, circleRadius, 0, 2 * Math.PI);
        ctx.stroke();

        // Upward force (ρVg)
        drawArrow(ctx, fbd_X, fbd_Y, fbd_X, fbd_Y - forceLen, arrowHeadSize);
        ctx.font = italicFont;
        ctx.textAlign = 'left';
        ctx.fillText('ρVg', fbd_X + 15, fbd_Y - forceLen);
        
        // Downward force (mg)
        drawArrow(ctx, fbd_X, fbd_Y, fbd_X, fbd_Y + forceLen, arrowHeadSize);
        ctx.fillText('mg', fbd_X + 15, fbd_Y + forceLen - 5);
        
        // 5. Caption
        ctx.font = captionFont;
        ctx.textAlign = 'center';
        ctx.fillText('力图 7.2.1', canvas.width / 2, canvas.height - 30);
    </script>
</body>
</html>